package com.server.http.service.imlp;

import com.server.dao.*;
import com.server.http.anYuan.AnYuanServer;
import com.server.http.service.AlarmService;
import com.server.http.service.UnitService;
import com.server.libs.login.AppOline;
import com.server.pojo.Alarm;
import com.server.pojo.MobileApp;
import com.server.pojo.MobileAppAlarm;
import com.server.push.AliYunPush;
import com.server.push.OnlinePush;
import com.server.push.dto.resp.AlarmOP;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

@Service
@Slf4j
@Transactional
public class AlarmServiceImpl implements AlarmService {
    @Autowired
    MobileAppAlarmDao mobileAppAlarmDao;
    @Autowired
    MobileAppUnitDao mobileAppUnitDao;

    @Autowired
    AlarmDao alarmDao;
    @Autowired
    MobileAppDao mobileAppDao;

    @Autowired
    UnitDao unitDao;

    @Autowired
    UnitService unitService;

    @Autowired
    OnlinePush onlinePush;
    @Autowired
    AppOline appOline;


    @Override
    @Transactional
    public Alarm push(Alarm alarm) {


        Set<MobileApp> mobileApps = new HashSet<>();

        /* 处理需要关联的App */
        if (alarm.getScope() != null) {
            List<MobileApp> scope = mobileAppDao.findScope(alarm.getLatitude(), alarm.getLongitude(), 0L, alarm.getScope());
            mobileApps.addAll(scope);
        }else {
            mobileApps.addAll(mobileAppUnitDao.getMobileApps(alarm.getUnit()));
        }
        mobileApps.addAll(mobileAppDao.findByReceivedAllIsTrue());
        /* ----End---- */


        return this.push(alarm,mobileApps);
    }


    @Override
    @Transactional
    public Alarm push(Alarm alarm, Set<MobileApp> mobileApps) {

        /* 关联App */
        Set<MobileAppAlarm> mobileAppAlarms = new HashSet<>();
        mobileApps.forEach((var)->{
            mobileAppAlarms.add(new MobileAppAlarm().setAlarm(alarm).setMobileApp(var));
        });
        mobileAppAlarmDao.saveAll(mobileAppAlarms);
        /* ----End---- */


        /*设置用户当前警报 并推送*/
        for (MobileApp mobileApp : mobileApps) {
            if (alarm.getInform() && mobileApp.getNowAlarm() == null) {  //通知
                mobileApp.setNowAlarm(alarm);
            }
        }
        mobileAppDao.saveAll(mobileApps);
        if (alarm.getAnYuanPushInterval() > 0) {
            /*通知安元平台*/
            List<MobileApp> m1 = mobileAppAlarmDao.getMobileApps(alarm);
            ScheduledExecutorService executor = Executors.newSingleThreadScheduledExecutor();
            executor.scheduleAtFixedRate(() -> {
                if (alarm.isExpired()) {
                    executor.shutdown(); // 如果满足退出条件，关闭执行器
                    return;
                }

                AnYuanServer.sendLocations(m1);
            }, 0, alarm.getAnYuanPushInterval(), TimeUnit.MILLISECONDS);
            /* ----End---- */
        }
        List<MobileApp> onlineApps = mobileApps.stream()
                .filter(app -> appOline.getMobileApps().contains(app))
                .collect(Collectors.toList());
        List<MobileApp> offlineApps = mobileApps.stream()
                .filter(app -> !appOline.getMobileApps().contains(app))
                .collect(Collectors.toList());

        AliYunPush.alarm(offlineApps, alarm);
        onlinePush.send(onlineApps, new AlarmOP(alarm));

        log.info("新警报-"+alarm.getUnit().getName()+"-"+ mobileApps.stream().map(MobileApp::getAccount).collect(Collectors.toList()));
        return alarm;
    }
}
